<!DOCTYPE html>
<html>
<head>
<title>Ubuntu-14.04-SVN-Server的安装和使用_MarkdownPad2</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<style type="text/css">
<style type="text/css">
/* GitHub stylesheet for MarkdownPad (http://markdownpad.com) */
/* Author: Nicolas Hery - http://nicolashery.com */
/* Version: b13fe65ca28d2e568c6ed5d7f06581183df8f2ff */
/* Source: https://github.com/nicolahery/markdownpad-github */

/* RESET
=============================================================================*/

html, body, div, span, applet, object, iframe, h1, h2, h3, h4, h5, h6, p, blockquote, pre, a, abbr, acronym, address, big, cite, code, del, dfn, em, img, ins, kbd, q, s, samp, small, strike, strong, sub, sup, tt, var, b, u, i, center, dl, dt, dd, ol, ul, li, fieldset, form, label, legend, table, caption, tbody, tfoot, thead, tr, th, td, article, aside, canvas, details, embed, figure, figcaption, footer, header, hgroup, menu, nav, output, ruby, section, summary, time, mark, audio, video {
  margin: 0;
  padding: 0;
  border: 0;
}

/* BODY
=============================================================================*/

body {
  font-family: Helvetica, arial, freesans, clean, sans-serif;
  font-size: 15px;
  line-height: 1.6;
  color: #333;
  background-color: #fff;
  padding: 20px;
  max-width: 960px;
  margin: 0 auto;
}

body>*:first-child {
  margin-top: 0 !important;
}

body>*:last-child {
  margin-bottom: 0 !important;
}

/* BLOCKS
=============================================================================*/

p, blockquote, ul, ol, dl, table, pre {
  margin: 15px 0;
}

/* HEADERS
=============================================================================*/

h1, h2, h3, h4, h5, h6 {
  margin: 20px 0 10px;
  padding: 0;
  font-weight: bold;
  -webkit-font-smoothing: antialiased;
}

h1 tt, h1 code, h2 tt, h2 code, h3 tt, h3 code, h4 tt, h4 code, h5 tt, h5 code, h6 tt, h6 code {
  font-size: inherit;
}

h1 {
  font-size: 28px;
  color: #000;
}

h2 {
  font-size: 24px;
  border-bottom: 1px solid #ccc;
  color: #000;
}

h3 {
  font-size: 18px;
}

h4 {
  font-size: 16px;
}

h5 {
  font-size: 14px;
}

h6 {
  color: #777;
  font-size: 14px;
}

body>h2:first-child, body>h1:first-child, body>h1:first-child+h2, body>h3:first-child, body>h4:first-child, body>h5:first-child, body>h6:first-child {
  margin-top: 0;
  padding-top: 0;
}

a:first-child h1, a:first-child h2, a:first-child h3, a:first-child h4, a:first-child h5, a:first-child h6 {
  margin-top: 0;
  padding-top: 0;
}

h1+p, h2+p, h3+p, h4+p, h5+p, h6+p {
  margin-top: 10px;
}

/* LINKS
=============================================================================*/

a {
  color: #4183C4;
  text-decoration: none;
}

a:hover {
  text-decoration: underline;
}

/* LISTS
=============================================================================*/

ul, ol {
  padding-left: 30px;
}

ul li > :first-child,
ol li > :first-child,
ul li ul:first-of-type,
ol li ol:first-of-type,
ul li ol:first-of-type,
ol li ul:first-of-type {
  margin-top: 0px;
}

ul ul, ul ol, ol ol, ol ul {
  margin-bottom: 0;
}

dl {
  padding: 0;
}

dl dt {
  font-size: 14px;
  font-weight: bold;
  font-style: italic;
  padding: 0;
  margin: 15px 0 5px;
}

dl dt:first-child {
  padding: 0;
}

dl dt>:first-child {
  margin-top: 0px;
}

dl dt>:last-child {
  margin-bottom: 0px;
}

dl dd {
  margin: 0 0 15px;
  padding: 0 15px;
}

dl dd>:first-child {
  margin-top: 0px;
}

dl dd>:last-child {
  margin-bottom: 0px;
}

/* CODE
=============================================================================*/

pre, code, tt {
  font-size: 12px;
  font-family: Consolas, "Liberation Mono", Courier, monospace;
}

code {
  font-size: 14px;
  margin: 0 0px;
  padding: 3px 5px;
  white-space: nowrap;
  border: 1px solid #e0e0e0;
  background-color: #f2f2f2;
  border-radius: 3px;
  text-decoration: none;
  color: #880022;
}

tt {
  margin: 0 0px;
  padding: 3px 5px;
  white-space: nowrap;
  border: 1px solid #e0e0e0;
  background-color: #f0f0f0;
  border-radius: 3px;
}

pre>code {
  margin: 0;
  padding: 0;
  white-space: pre;
  border: none;
  background: transparent;
}

pre {
  background-color: #f8f8f8;
  border: 1px solid #ccc;
  font-size: 13px;
  line-height: 19px;
  overflow: auto;
  padding: 6px 10px;
  border-radius: 3px;
}

pre code, pre tt {
  background-color: transparent;
  border: none;
}

kbd {
    -moz-border-bottom-colors: none;
    -moz-border-left-colors: none;
    -moz-border-right-colors: none;
    -moz-border-top-colors: none;
    background-color: #DDDDDD;
    background-image: linear-gradient(#F1F1F1, #DDDDDD);
    background-repeat: repeat-x;
    border-color: #DDDDDD #CCCCCC #CCCCCC #DDDDDD;
    border-image: none;
    border-radius: 2px 2px 2px 2px;
    border-style: solid;
    border-width: 1px;
    font-family: "Helvetica Neue",Helvetica,Arial,sans-serif;
    line-height: 10px;
    padding: 1px 4px;
}

/* QUOTES
=============================================================================*/

blockquote {
  border-left: 4px solid #DDD;
  padding: 0 15px;
  color: #777;
}

blockquote>:first-child {
  margin-top: 0px;
}

blockquote>:last-child {
  margin-bottom: 0px;
}

/* HORIZONTAL RULES
=============================================================================*/

hr {
  clear: both;
  margin: 15px 0;
  height: 0px;
  overflow: hidden;
  border: none;
  background: transparent;
  border-bottom: 4px solid #ddd;
  padding: 0;
}

/* TABLES
=============================================================================*/

table th {
  font-weight: bold;
}

table th, table td {
  border: 1px solid #ccc;
  padding: 6px 13px;
}

table tr {
  border-top: 1px solid #ccc;
  background-color: #fff;
}

table tr:nth-child(2n) {
  background-color: #f8f8f8;
}

/* IMAGES
=============================================================================*/

img {
  max-width: 100%
}
</style>
</style>
<base href='./'/>
</head>
<body>
<h1>Ubuntu 14.04 SVN Server 的安装和使用</h1>
<h1>1. 安装 SVN</h1>
<h2>1.1. SVN 的安装</h2>
<pre><code>$ sudo apt-get install subversion
</code></pre>

<h2>1.2. SVN 根目录</h2>
<p>例如，我们把 <code>/home/skyinno/svn/</code> 作为 <code>SVN</code> ，创建该目录，命令如下：</p>
<pre><code>$ mkdir -p /home/skyinno/svn
</code></pre>

<h3>1.2.1. 为 SVN 根目录软连接</h3>
<p>（注：一般情况下请跳过这一步，不是必须的，这是笔者的特殊需求。）</p>
<p>由于服务器的 <code>系统盘</code> 容量比较小，不希望 <code>SVN</code> 仓库的目录占用 <code>系统盘</code> 的空间，所以我们把 <code>/home/skyinno/svn</code> 软连接到 <code>/data/svn</code> 目录。（这里 <code>/data</code> 目录所在的磁盘容量比较大，共有 <code>35TB</code>。）</p>
<p>先在 <code>/data</code> 目录下创建 <code>svn</code> 目录：</p>
<pre><code>$ sudo mkdir -p /data/svn
</code></pre>

<p>然后设置软连接，把 <code>/home/skyinno/svn</code> 软连接到 <code>/data/svn</code> 目录：</p>
<pre><code>$ sudo ln -s /data/svn /home/skyinno/svn
</code></pre>

<p>当然，这里要求 <code>/home/skyinno/svn</code> 不能存在，如果 <code>/home/skyinno/svn</code> 文件夹已经存在，上面的命令会报错。如果该文件夹里面是空的，什么都没有，则可以使用 <code>rm</code> 命令直接删除该目录；如果不是空的，先把原来的 <code>/home/skyinno/svn</code> 目录改名为 <code>/home/skyinno/svn.old</code>，再把 <code>/home/skyinno/svn.old</code> 目录里的内容复制到 <code>/data/svn/</code> 目录下面，再做软连接。具体步骤如下：</p>
<pre><code>$ sudo mv /home/skyinno/svn /home/skyinno/svn.old
$ sudo cp -r /home/skyinno/svn.old/. /data/svn/
$ sudo ln -s /data/svn /home/skyinno/svn
</code></pre>

<h1>2. 配置和使用 SVN</h1>
<h2>2.1. 创建 SVN 仓库</h2>
<p>创建一个名为 <code>myrepo</code> 的仓库：</p>
<pre><code>$ sudo svnadmin create /home/skyinno/svn/myrepo
</code></pre>

<p>然后查看一下 <code>myrepo</code> 目录里的文件：</p>
<pre><code>$ cd /home/skyinno/svn/myrepo
$ ll -h

drwxr-xr-x 2 root root 4096 Oct 21 14:28 conf/
drwxr-sr-x 6 root root 4096 Oct 21 14:29 db/
-r--r--r-- 1 root root    2 Oct 21 14:28 format
drwxr-xr-x 2 root root 4096 Oct 21 14:28 hooks/
drwxr-xr-x 2 root root 4096 Oct 21 14:28 locks/
-rw-r--r-- 1 root root  246 Oct 21 14:28 README.txt
</code></pre>

<p>进入 <code>/conf</code> 目录，这个目录下存放的都是这个仓库的配置文件：</p>
<pre><code>$ cd conf
$ ll -h

-rw-r--r-- 1 root root 1080 Oct 21 14:28 authz
-rw-r--r-- 1 root root  885 Oct 21 14:28 hooks-env.tmpl
-rw-r--r-- 1 root root  309 Oct 21 14:28 passwd
-rw-r--r-- 1 root root 4002 Oct 21 14:28 svnserve.conf
</code></pre>

<p>其中 <code>svnserve.conf</code> 是 <code>SVN</code> 仓库的一些设置，<code>passwd</code> 是验证用户的用户名和密码，是明文的，未加密。<code>authz</code> 是验证和读写权限相关的设置。</p>
<h2>2.2. 配置 SVN 仓库</h2>
<p>我们只需要修改 <code>svnserve.conf</code> 和 <code>passwd</code> 文件即可，<code>authz</code> 的配置稍微复杂一点，此处不详细介绍。</p>
<p>编辑 <code>svnserve.conf</code> 文件：</p>
<pre><code>$ cd /home/skyinno/svn/myrepo
$ cd conf
$ sudo vim svnserve.conf
</code></pre>

<p>找到配置文件里分别包含以下三行的语句：</p>
<pre><code># anon-access = read
# auth-access = write

# password-db = passwd
</code></pre>

<p>把前面的注释 “<code>#</code> ” 去掉，记得顶格（最前面不能有空格），并修改为如下形式，<code>read</code> 改为 <code>none</code>：</p>
<pre><code>anon-access = none
auth-access = write

password-db = passwd
</code></pre>

<p>这里，我们不希望匿名用户浏览和访问仓库，所以 <code>anon-access</code> 设置为 <code>none</code>，一般默认设置为 <code>read</code> 。更详细的解释为：</p>
<pre><code># 如果[general]前面有#号，则去掉#号（注释）
[general]

# 匿名访问的权限，可以是 read, write, none, 默认为 read。
# 设置成 none 的意思就是不允许匿名用户访问（读/写）
anon-access = none

# 认证用户的权限，可以是 read, write, none, 默认为 write。
auth-access = write

# 密码数据库的路径，去掉前面的 “# ”
password-db = passwd
</code></pre>

<p>修改 <code>passwd</code> 文件，配置用户名和密码：</p>
<pre><code>$ cd /home/skyinno/svn/myrepo
$ cd conf
$ sudo vim passwd

[users]
# harry = harryssecret
# sally = sallyssecret
shines77 = abcd5678
xiaoji = abcd1234
</code></pre>

<p>最好按这个格式，前面顶格，<code>=</code> 号之间保留空格，以免出现不必要的错误。</p>
<h2>2.3. 启动 SVN 服务</h2>
<p>启动服务的命令：</p>
<pre><code>$ sudo svnserve -d -r /home/skyinno/svn
</code></pre>

<p>其中 <code>-d</code> 表示以 Daemon 方式启动，<code>-r</code> 后面是 <code>svn</code> 仓库的 <code>root</code> 目录。如果你的服务器不止一个 <code>IP</code>，还可以指定要绑定的 <code>IP</code> 地址，例如：</p>
<pre><code>$ sudo svnserve -d -r /home/skyinno/svn --listen-host 192.168.3.225
</code></pre>

<p>检查 <code>SVN</code> 服务是否已经启动了，可以使用命令：</p>
<pre><code>$ netstat -ntlp | grep 3690

tcp     0     0 0.0.0.0:3690    0.0.0.0:*       LISTEN     16630/svnserve
</code></pre>

<p>关闭服务的命令：</p>
<pre><code>$ sudo killall -9 svnserve
</code></pre>

<p>如果想让 <code>SVN</code> 跟随系统开机自动启动，可以把 <code>svnserve</code> 的启动参数写到 <code>/etc/rc.local</code> 文件里，例如：</p>
<pre><code>$ sudo vim /etc/rc.local

# 此处文件头若干内容省略 ......

/usr/bin/svnserve -d -r /home/skyinno/svn
exit 0
</code></pre>

<h2>2.4. 导入 SVN 仓库</h2>
<p>前面只是在 <code>SVN</code> 服务器创建了一个名为 <code>myrepo</code> 的仓库而已，现在来说说怎么从客户端导入文件到 <code>SVN</code> 服务器的仓库上。</p>
<p>为了测试方便，我们可以直接在服务器上建个目录，并创建一个叫 <code>ReadMe.txt</code> 的文件，然后来测试导入，例如：</p>
<pre><code>$ mkdir -p /home/skyinno/svn_repo/myrepo/
$ cd /home/skyinno/svn_repo/myrepo/
$ vim ReadMe.txt
</code></pre>

<p>在 <code>ReadMe.txt</code> 文件里随意输入几个字母即可，保存退出，然后执行下面的命令，把目录 <code>/home/skyinno/svn_repo/myrepo/</code> 导入到服务器上的 <code>myrepo</code> 仓库里：</p>
<pre><code>$ sudo svn import -m &quot;first submit.&quot; /home/skyinno/svn_repo/myrepo/ file:///home/skyinno/svn/myrepo/

Adding         /home/skyinno/svn_repo/myrepo/ReadMe.txt
Committed revision 1.
</code></pre>

<p>导入命令的具体格式是：</p>
<pre><code>$ sudo svn import -m &quot;本次提交的详细描述信息&quot; {本地仓库的路径} {远端仓库的URL}
</code></pre>

<p>如果 <code>远端仓库的URL</code> 就在同一台服务器上，则可以使用 <code>file://</code> 前缀修饰。</p>
<h2>2.5. 导出 SVN 仓库</h2>
<p>在远程的机器上安装 <code>SVN</code> 客户端，来测试 <code>SVN</code> 仓库的导出，例如：<code>Windows</code> 下安装 <code>TortoiseSVN</code>，下载地址是：<a href="http://tortoisesvn.tigris.org/">http://tortoisesvn.tigris.org/</a>。</p>
<p>在需要导出的目录的空白处，点击鼠标右键，选出 <code>SVN 检出</code> (<code>SVN Checkout</code>)，然后输入 “<code>svn://192.168.3.225/myrepo/</code>”，回车确定，即可完成导出。</p>
<p>如果没有 <code>GUI</code> 环境，也可以通过命令行来导出：</p>
<pre><code>$ svn checkout svn://192.168.3.225/myrepo --username=shines77
</code></pre>

<p>或者将 <code>checkout</code> 缩写为 <code>co</code>，即：</p>
<pre><code>$ svn co svn://192.168.3.225/myrepo --username=shines77
</code></pre>

<h1>3. 使用 Apache 配置 SVN</h1>
<h2>3.1. 安装组件</h2>
<p>先安装必要的组件：</p>
<pre><code>$ sudo apt-get install apache2 libapache2-svn
</code></pre>

<h2>3.2. 修改配置</h2>
<p>然后修改 <code>/etc/apache2/mods-available/dav_svn.conf</code> 文件，在后面添加如下内容：</p>
<pre><code>$ sudo vim /etc/apache2/mods-available/dav_svn.conf

&lt;Location /svn/myrepo&gt;

  DAV svn
  #SVNPath /home/skyinno/svn/myrepo
  SVNParentPath /home/skyinno/svn
  AuthType Basic
  AuthName &quot;My Subversion Repository&quot;
  AuthUserFile /etc/apache2/dav_svn.passwd

  #&lt;LimitExcept GET PROPFIND OPTIONS REPORT&gt;
    Require valid-user
  #&lt;/LimitExcept&gt;

&lt;/Location&gt;
</code></pre>

<p>注：如果需要用户每次登录时都进行用户密码验证，请将 <code>&lt;LimitExcept GET PROPFIND OPTIONS REPORT&gt;</code> 与 <code>&lt;/LimitExcept&gt;</code> 两行注释掉。</p>
<p>此外，<code>SVNPath</code> 和 <code>SVNParentPath</code> 你只能选择一个，两个同时设置会报错，推荐只设置 <code>SVNParentPath</code> 的值。</p>
<p>保存完上面的文件以后，你需要重启一下 <code>Apache2</code> 服务：</p>
<pre><code>$ sudo /etc/init.d/apache2 restart
或者
$ sudo service apache2 restart
</code></pre>

<h2>3.3. 设置验证密码</h2>
<p>在前面的 <code>dav_svn.conf</code> 文件里，我们把验证用户的文件定义为 <code>/etc/apache2/dav_svn.passwd</code>，该文件包含了用户授权的详细信息（密码是加密的）。我们现在开始编辑它，命令格式如下：</p>
<pre><code>$ sudo htpasswd -c /etc/apache2/dav_svn.passwd {user_name}
</code></pre>

<p>其中，<code>-c</code> 代表是新建 <code>passwd</code> 文件（会删掉旧的文件），所以这个参数只是在添加第一个用户的使用，否则旧的授权信息就被删掉了。，例如：</p>
<pre><code>$ sudo htpasswd -c /etc/apache2/dav_svn.passwd shines77
$ sudo htpasswd /etc/apache2/dav_svn.passwd xiaoji
$ sudo htpasswd /etc/apache2/dav_svn.passwd xiaoming
$ sudo htpasswd /etc/apache2/dav_svn.passwd xiaocai
$ sudo htpasswd /etc/apache2/dav_svn.passwd xiaowu
$ sudo htpasswd /etc/apache2/dav_svn.passwd xiaohan
$ sudo htpasswd /etc/apache2/dav_svn.passwd xiaodong
$ sudo htpasswd /etc/apache2/dav_svn.passwd xiaoguo
$ sudo htpasswd /etc/apache2/dav_svn.passwd guest
</code></pre>

<p>可以看到，创建第二个和第二个以后的用户信息时，都没有添加 <code>-c</code> 参数。</p>
<p>然后你就可以通过浏览器访问如下地址：</p>
<pre><code>http://localhost/svn/myrepo
</code></pre>

<p>其中 <code>localhost</code> 改成你的 <code>SVN</code> 服务器的 <code>IP</code> 地址即可。</p>
<h1>4. 参考文章</h1>
<ol>
<li>
<p>Ubuntu 下 SVN 安装和配置<br/>
<a href="http://zhan.renren.com/itbegin?gid=3602888498033631485&amp;checked=true">http://zhan.renren.com/itbegin?gid=3602888498033631485&amp;checked=true</a></p>
</li>
<li>
<p>Ubuntu 下搭建 SVN 服务器（Subversion）<br/>
<a href="https://my.oschina.net/huangsz/blog/176128">https://my.oschina.net/huangsz/blog/176128</a></p>
</li>
<li>
<p>Ubuntu 安装和配置 SVN （里面有对如何配置 <code>authz</code> 文件更详细的说明）<br/>
<a href="http://www.cnblogs.com/wuhou/archive/2008/09/30/1302471.html">http://www.cnblogs.com/wuhou/archive/2008/09/30/1302471.html</a></p>
</li>
<li>
<p>SVN 命令使用详解<br/>
<a href="http://blog.sina.com.cn/s/blog_963453200101eiuq.html">http://blog.sina.com.cn/s/blog_963453200101eiuq.html</a></p>
</li>
</ol>
<p>.</p>
</body>
</html>
<!-- This document was created with MarkdownPad, the Markdown editor for Windows (http://markdownpad.com) -->
